package ffte.core.streamed

import spinal.core._
import spinal.lib._

import ffte.types.VecComplex
import ffte.property.{getFFTIW,getFFTOW}
import ffte.algorithm.FFTGen.{Method,genericFT,DFT,psbFFT,msbFFT,wpbFFT}

/**
 * Streamed FFT implementation method
 *
 * This class provides the core implementation method for generating streamed (pipelined)
 * FFT hardware components from abstract algorithm specifications. The streamed architecture
 * processes data in a pipelined fashion with flow control, enabling continuous data
 * processing with high throughput and predictable latency.
 *
 * Architecture Characteristics:
 * - Pipelined processing: Multiple data samples in flight simultaneously
 * - Flow control: Ready/valid handshaking for backpressure support
 * - Fragment support: Handles burst data transfers with last signal
 * - Group processing: Processes multiple samples per clock cycle for efficiency
 *
 * Performance Benefits:
 * - High throughput: Continuous data processing capability
 * - Predictable latency: Fixed pipeline depth
 * - Backpressure support: Handles downstream congestion gracefully
 * - Scalable performance: Throughput scales with group size
 *
 * Algorithm Support:
 * - DFT: Direct DFT implementation for basic transforms
 * - psbFFT[Streamed]: Prime-space decomposition with streaming architecture
 * - msbFFT[Streamed]: Mixed-space decomposition with streaming architecture
 * - wpbFFT[Streamed]: Winograd prime-based decomposition with streaming architecture
 * - Default fallback to 2-point streamed DFT for unknown types
 *
 * @param shift Scaling shift amount for fixed-point overflow prevention
 */
class Streamed(shift: Int) extends Method {
    /**
     * Generate streamed FFT component from algorithm specification
     *
     * This method serves as the factory for creating concrete streamed FFT hardware
     * components from abstract algorithm specifications. It uses pattern matching
     * to select the appropriate streamed implementation based on the FFT algorithm type.
     *
     * Implementation Selection Logic:
     * - DFT: Direct streamed DFT implementation for basic transforms
     * - psbFFT[Streamed]: Prime-space decomposition with Chinese Remainder Theorem
     * - msbFFT[Streamed]: Mixed-space decomposition using Cooley-Tukey algorithms
     * - wpbFFT[Streamed]: Winograd prime-based decomposition for optimal multiplication count
     * - Fallback: 2-point streamed DFT for unsupported algorithm types
     *
     * All implementations use the streamed architecture for consistent
     * high-throughput performance with flow control support.
     *
     * @param entity Abstract FFT algorithm specification
     * @param prefix Naming prefix for generated components (for debugging/identification)
     * @return Concrete streamed FFT component with streaming interface
     */
    def apply(entity: genericFT, prefix: String): streamedComponents = {
        entity match {
            case d: DFT =>
                // Direct streamed DFT implementation for small transforms or reference cases
                new sdft2(shift)
            case d: psbFFT[Streamed] =>
                // Prime-space decomposition (Chinese Remainder Theorem based)
                new psb(shift, d)
            case d: msbFFT[Streamed] =>
                // Mixed-space decomposition (Cooley-Tukey based)
                new msb(shift, d)
            case d: wpbFFT[Streamed] =>
                // Winograd prime-based decomposition (optimal multiplication count)
                new wpb(shift, d)
            case _ =>
                // Fallback to 2-point streamed DFT for unknown algorithm types
                new sdft2(shift)
        }
    }
}

